#include "logicplayer.h"
#include"networkmanager.h"
#include"messageconst.h"

DEFINE_SINGLE_ATTRIBUTES(LogicPlayer);

LogicPlayer::LogicPlayer()
{
    NET_INSTANCE()->add(MESSAGE_PLAYER_LEAVE,handler(this,SEL_EVENTFUNC(LogicPlayer::c2sPlayerLeave)));
    NET_INSTANCE()->add(MESSAGE_INIT_DATA,handler(this,SEL_EVENTFUNC(LogicPlayer::c2sInitData)));
    NET_INSTANCE()->add(MESSAGE_INIT_POS,handler(this,SEL_EVENTFUNC(LogicPlayer::c2sInitPos)));
    NET_INSTANCE()->add(MESSAGE_MOVE_TO,handler(this,SEL_EVENTFUNC(LogicPlayer::LogicPlayer::c2sMoveTo)));
    NET_INSTANCE()->add(MESSAGE_UPDATE_DATA,handler(this,SEL_EVENTFUNC(LogicPlayer::LogicPlayer::c2sUpdateData)));
    NET_INSTANCE()->add(MESSAGE_VERIFY_POS,handler(this,SEL_EVENTFUNC(LogicPlayer::LogicPlayer::c2sVertifyPos)));
}

void LogicPlayer::c2sPlayerLeave(Json::Value&)
{
    int fd=NET_INSTANCE()->getFd();
    auto& playermaps=NET_SOCKET().m_playermaps;
    cout<<playermaps[fd].rolename<<" off line"<<endl;
    for(auto var:playermaps)
    {
        if(var.first!=fd)
        {
            NetMsg msg;
            msg["fd"]=fd;
            NET_INSTANCE()->send(var.first,MESSAGE_PLAYER_LEAVE,msg);
        }
    }
    playermaps.erase(fd);
}

void LogicPlayer::c2sInitData(Json::Value& msg)
{
    int fd=NET_INSTANCE()->getFd();
    auto& playermaps=NET_SOCKET().m_playermaps;
    playermaps[fd].playername=msg["playername"].asString();
    playermaps[fd].rolename=msg["rolename"].asString();
    playermaps[fd].playertype=msg["playertype"].asString();
    playermaps[fd].curmap=msg["curmap"].asInt();
    playermaps[fd].blood=msg["blood"].asFloat();
    playermaps[fd].mana=msg["mana"].asFloat();
    playermaps[fd].attack=msg["attack"].asFloat();
    playermaps[fd].defense=msg["defense"].asFloat();
    playermaps[fd].grade=msg["grade"].asInt();
    cout<<msg["playername"].asString()<<":"<<msg["rolename"].asString()<<" online!"<<endl;
    for(auto var:playermaps)
    {
        if(var.first!=fd)
        {
           NetMsg smsg;
           smsg["playername"]=playermaps[var.first].playername;
           smsg["rolename"]=playermaps[var.first].rolename;
           smsg["playertype"]=playermaps[var.first].playertype;
           smsg["curmap"]=playermaps[var.first].curmap;
           smsg["blood"]=playermaps[var.first].blood;
           smsg["mana"]=playermaps[var.first].mana;
           smsg["attack"]=playermaps[var.first].attack;
           smsg["defense"]=playermaps[var.first].defense;
           smsg["grade"]=playermaps[var.first].grade;
           smsg["fd"]=var.first;
           NET_INSTANCE()->send(fd,MESSAGE_INIT_DATA,smsg); //SendMsg(fd,(char*)&smsg,sizeof(smsg));
           msg["fd"]=fd;
           NET_INSTANCE()->send(var.first,MESSAGE_INIT_DATA,msg);
//           SendMsg(var.first,(char*)rlmsg,sizeof(InitData_Msg));
        }
    }
}

void LogicPlayer::c2sInitPos(Json::Value& msg)
{
    int fd=NET_INSTANCE()->getFd();
    auto& playermaps=NET_SOCKET().m_playermaps;
    playermaps[fd].x=msg["x"].asFloat();
    playermaps[fd].y=msg["y"].asFloat();
    playermaps[fd].curmap=msg["curmap"].asInt();
    cout<<playermaps[fd].rolename<<" initialize position("<<msg["x"].asFloat()<<","<<msg["y"].asFloat()<<")"<<endl;
    for(auto var:playermaps)
    {
        if(var.first!=fd)
        {
            msg["fd"]=fd;
            NET_INSTANCE()->send(var.first,MESSAGE_INIT_POS,msg);
            //SendMsg(var.first,(char*)msg,sizeof(InitPos_Msg));
            NetMsg smsg;
            smsg["fd"]=var.first;
            smsg["x"]=playermaps[var.first].x;
            smsg["y"]=playermaps[var.first].y;
            smsg["curmap"]=playermaps[var.first].curmap;
            NET_INSTANCE()->send(fd,MESSAGE_INIT_POS,smsg);
            //SendMsg(fd,(char*)&smsg,sizeof(smsg));
        }
    }
}

void LogicPlayer::c2sMoveTo(Json::Value& msg)
{
    int fd=NET_INSTANCE()->getFd();
    auto& playermaps=NET_SOCKET().m_playermaps;
    cout<<playermaps[fd].rolename<<" move to position("<<msg["x"].asFloat()<<","<<msg["y"].asFloat()<<")"<<endl;
    for(auto var:playermaps)
    {
        if(var.first!=fd)
        {
            msg["fd"]=fd;
            NET_INSTANCE()->send(var.first,MESSAGE_MOVE_TO,msg);
            //SendMsg(var.first,(char*)msg,sizeof(MoveTo_Msg));
        }
    }
}

void LogicPlayer::c2sVertifyPos(Json::Value& msg)
{
    int fd=NET_INSTANCE()->getFd();
    auto& playermaps=NET_SOCKET().m_playermaps;
    cout<<playermaps[fd].rolename<<" verify position("<<msg["x"].asFloat()<<","<<msg["y"].asFloat()<<")"<<endl;
    for(auto var:playermaps)
    {
        if(var.first!=fd)
        {
            msg["fd"]=fd;
            NET_INSTANCE()->send(var.first,MESSAGE_VERIFY_POS,msg);
            //SendMsg(var.first,(char*)msg,sizeof(VerifyPos_Msg));
        }
        else
        {
            playermaps[var.first].x=msg["x"].asFloat();
            playermaps[var.first].y=msg["y"].asFloat();
        }
    }
}

void LogicPlayer::c2sUpdateData(Json::Value& msg)
{
    int fd=NET_INSTANCE()->getFd();
    auto& playermaps=NET_SOCKET().m_playermaps;
    playermaps[fd].attack=msg["attack"].asFloat();
    playermaps[fd].blood=msg["blood"].asFloat();
    playermaps[fd].defense=msg["defense"].asFloat();
    playermaps[fd].grade=msg["grade"].asInt();
    playermaps[fd].mana=msg["mana"].asFloat();
    msg["fd"]=fd;
    cout<<playermaps[fd].rolename<<" update data"<<endl;
    for(auto var:playermaps)
    {
        if(var.first!=fd)
        {
            NET_INSTANCE()->send(var.first,MESSAGE_UPDATE_DATA,msg);
            //SendMsg(var.first,(char*)msg,sizeof(UpdateData_Msg));
        }
    }
}
